package net.homelinux.chaoswg.io.renga.core;

import java.io.File;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.Arrays;
import java.util.jar.Attributes;
import java.util.jar.JarFile;

import net.homelinux.chaoswg.io.renga.core.gui.GUI;
import net.homelinux.chaoswg.io.renga.core.gui.operations.CompositeOperation;
import net.homelinux.chaoswg.io.renga.core.gui.operations.Control;
import net.homelinux.chaoswg.io.renga.core.registries.GlobalPropertyRegistry;

public class Starter {
    public Starter (final String... args)  {
        try {
            new Test().apply();
            
            parseArgs (args);
            GlobalPropertyRegistry gpr = GlobalPropertyRegistry.getGlobalPropertyRegistry();
            gpr.setProperty("animationStatus", true);
            gpr.setProperty("animationSpeed", 5);            
            new GUI(new CompositeOperation(new Control ()));
        } catch (CommandLineArgumentException e) {
		System.out.println ("Exception");
            showUsage();
        }
//      new GUI(new CompositeOperation(new Control ()));
    }


    private void parseArgs (final String... args) throws CommandLineArgumentException {
        for (int i = 0, n = args.length; i < n; ++i) {
            if (args[i].equals ("-x")) {
                if (i+1 < n) {
                    initializeExtensions(args[i+1]);
                    ++i;
                } else {
                    throw new CommandLineArgumentException ("Wrong usage");
                }
            }
        }
    }

    private URL[] generateURLs (String... args) {
        final URL [] toReturn = new URL [args.length];

        for (int i = 0, n = toReturn.length; i < n; ++i) {
            final File f = new File (args[i]);
            try {
                toReturn[i] = f.toURL();
            } catch (MalformedURLException murlexcp) {
                System.err.println("Can't load " + args[i]);
            }
        }

        return toReturn;
    }

    private void initializeExtensions (final String args) {
        final String argsSplit [] = args.split(System.getProperty("path.separator"));
        final URL [] jarURLS =generateURLs (argsSplit);

        final URLClassLoader classLoader = new URLClassLoader (jarURLS);
        GlobalPropertyRegistry.getGlobalPropertyRegistry().setProperty("ClassLoader", classLoader);

        for (final String jarFileName : argsSplit) {
            try {
                final JarFile f = new JarFile (jarFileName);
                final Attributes attributes = f.getManifest().getMainAttributes();
                final String className = attributes.getValue("Initializer");

                Class initializer = classLoader.loadClass(className);  
                if (Arrays.asList(initializer.getInterfaces()).contains (Initializer.class)) {
                    ((Initializer)initializer.newInstance()).apply();
                    System.out.println("Loaded " + jarFileName);
                }
            } catch (Exception e) {
                System.err.println("Couldn't load " + jarFileName + " maybe it doesn't exist or it is not a valid extension.");
                //Nothing to be done here, one extension couldn't be loaded for some reason maybe the others will 
            }

        }
    }

    private static void showUsage () {
        System.out.println("USAGE");
        System.out.println();
        System.out.println("java /Path/to/Programm/Renga.jar -x Extension1"+  System.getProperty("path.separator")+  "Extension2"
                +System.getProperty("path.separator")+"Extension3"+System.getProperty("path.separator")+"...");
        System.out.println();
        System.out.println("Where ExtensionN is the path to a Jar-File containing a valid RENGA extension");
    }

    public static void main (String... args) {
        if (args.length > 0) {
            new Starter (args);
        } else  {
		System.out.println ("ARGS");
            showUsage();
        }       
    }
}
